package pms.dao;

import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.springframework.orm.hibernate3.HibernateTemplate;
import org.springframework.orm.hibernate3.support.HibernateDaoSupport;

import pms.om.Mitarbeiter;
import pms.om.MitarbeiterAbwesend;
import pms.om.Urlaubsanspruch;
import pms.om.Jahr;


public class MitarbeiterDao extends HibernateDaoSupport {
	
	/**
	 * R&uuml;ckgabe eines Mitarbeiters anhand seiner id
	 * @param id
	 * @return eines Mitarbeiters
	 */
	
	public Mitarbeiter findById(int id) {
		HibernateTemplate template = getHibernateTemplate();
		return (Mitarbeiter) template.get(Mitarbeiter.class, id);
	}
 	
	/**
	 * R&uuml;ckgabe aller Mitarbeiter 
	 * @return alle Mitarbeiter
	 */
	
	@SuppressWarnings("unchecked")
	public Set<Mitarbeiter> findAll() {
		HibernateTemplate template = getHibernateTemplate();
		List<Mitarbeiter> allemitarbeiter = template.loadAll(Mitarbeiter.class);
		Set<Mitarbeiter> results = new HashSet<Mitarbeiter>();
		for (Mitarbeiter mitarbeiter : allemitarbeiter) {
			results.add(mitarbeiter);			
		}
		return results;
	}
	
	/**
	 * R&uuml;ckgabe aller Mitarbeiter bis auf die, die bereits ausgetreten sind
	 * @return
	 */
	
	public Set<Mitarbeiter> findAllohneAustritt() {
		Set<Mitarbeiter> allemitarbeiter = findAll();
		Set<Mitarbeiter> results = new HashSet<Mitarbeiter>();
		Date aktuellesDatum = new Date();
		for (Mitarbeiter mitarbeiter : allemitarbeiter) {
			Date austrittsdatum = mitarbeiter.getAustrittsdatum();
			if (!(austrittsdatum == null)) {
				if (aktuellesDatum.compareTo(austrittsdatum) <= 0) {
					results.add(mitarbeiter);
				}
			}
			else {
				results.add(mitarbeiter);
			}
		}
		return results;
	}
	
	/**
	 * Einen neuen Mitarbeiter anlegen
	 * @param personalnummer
	 * @param anrede
	 * @param vorname
	 * @param nachname
	 * @param aufgabe_position
	 * @param geburtsdatum
	 * @param eintrittsdatum
	 * @param austrittsdatum
	 * @param e_mail_adresse
	 * @param telefon
	 * @param faxnummer
	 * @param passwort
	 */
	
	public void create(String personalnummer, String anrede, String vorname, String nachname, String aufgabe_position,
	                   Date geburtsdatum, Date eintrittsdatum, Date austrittsdatum, String e_mail_adresse,
	                   String telefon, String faxnummer, String passwort) {
		HibernateTemplate template = getHibernateTemplate();
		Mitarbeiter m = new Mitarbeiter(personalnummer, anrede, vorname, nachname, aufgabe_position,
				                        geburtsdatum, eintrittsdatum, austrittsdatum, e_mail_adresse, telefon,
				                        faxnummer, passwort);
		template.persist(m);
	}

	/**
	 * &auml;ndere Mitarbeiter mit einer bestimmten id auf die neu mit &uuml;bergebenen Eigenschaften um
	 * @param id
	 * @param personalnummer
	 * @param anrede
	 * @param vorname
	 * @param nachname
	 * @param aufgabe_position
	 * @param geburtsdatum
	 * @param eintrittsdatum
	 * @param austrittsdatum
	 * @param e_mail_adresse
	 * @param telefon
	 * @param faxnummer
	 * @param passwort
	 */
	
	public void modify(int id, String personalnummer, String anrede, String vorname, String nachname, 
			           String aufgabe_position, Date geburtsdatum, Date eintrittsdatum, Date austrittsdatum, 
			           String e_mail_adresse, String telefon, String faxnummer, String passwort) {
		HibernateTemplate template = getHibernateTemplate();
		Mitarbeiter m = (Mitarbeiter) template.get(Mitarbeiter.class, id);
		m.setPersonalnummer(personalnummer);
		m.setAnrede(anrede);
		m.setVorname(vorname);
		m.setNachname(nachname);
		m.setAufgabe_position(aufgabe_position);
		m.setGeburtsdatum(geburtsdatum);
		m.setEintrittsdatum(eintrittsdatum);
		m.setAustrittsdatum(austrittsdatum);
		m.setE_mail_adresse(e_mail_adresse);
		m.setTelefon(telefon);
		m.setFaxnummer(faxnummer);
		m.setPasswort(passwort);
		template.saveOrUpdate(m);
		template.flush();
	}
	
	/**
	 * l&ouml;sche Mitarbeiter mit bestimmter id
	 * @param id
	 */
	
	public boolean deleteById(int id) {
		HibernateTemplate template = getHibernateTemplate();
		boolean result = false;
		Mitarbeiter m = findById(id);  // zunächste suche den Mitarbeiter mit der id
		template.delete(m);
		template.flush();
		return result;
	}
	
	/**
	 * Urlaubsanspr&uuml;che eines Mitarbeiters zur&uuml;ckgeben
	 * @param id
	 */
	public Set<Urlaubsanspruch> getUrlaubsanspruecheMitarbeiterbyId(int id) {		
		Mitarbeiter m = findById(id);
		return m.getUrlaubsanspruechedesmitarbeiters();
	}
	
	/**
	 * R&uuml;ckgabe des Set weniger des Mitarbeiters m
	 * @param m
	 * @param mset
	 */
	
	public Set<Mitarbeiter> findAllbisaufEinen(Mitarbeiter m, Set<Mitarbeiter> mset) {
		Set<Mitarbeiter> result = new HashSet<Mitarbeiter>();
    	for (Mitarbeiter mitarbeiter : mset) {
    		if (!mitarbeiter.equals(m)) {
    			result.add(mitarbeiter);
    		}	 
    	}
    	return result;
	}
	
	/**
	 * R&uuml;ckgabe aller Mitarbeiter ohne die Mitarbeiter des &uuml;bergebenen Sets
	 * @param mset
	 */
	
	public Set<Mitarbeiter> findeallemitarbeiterdienichtimSet(Set<Mitarbeiter> mset) {
		// zunächst alle Mitarbeiter in result speichern
		Set<Mitarbeiter> result = findAll();
		for (Mitarbeiter mitarbeiter : mset) {
			result = findAllbisaufEinen(mitarbeiter, result); 
		}
		return result;
	}

	
	
	public void setUrlaubstagefuerMitarbeiter(int id, Jahr jahr, int anzahltage) {
		HibernateTemplate template = getHibernateTemplate();
		Mitarbeiter m = findById(id);
		Set<Urlaubsanspruch> u = m.getUrlaubsanspruechedesmitarbeiters();
		u.add(new Urlaubsanspruch(anzahltage, jahr)); 
		m.setUrlaubsanspruechedesmitarbeiters(u);
		template.saveOrUpdate(m);
		template.flush();
	}

	
	public Set<MitarbeiterAbwesend> findeVorgemerkteAbwesenheiten(int idm) {
		Mitarbeiter m = findById(idm);		
		Set<MitarbeiterAbwesend> result = m.getAbwesenheitendesmitarbeiters();
		return result;
	}
	
	/**
	 * sind alle g&uuml;ltiges Datum?
	 * @param geburtsdatum
	 * @param eintrittsdatum
	 * @param austrittsdatum
	 */
	
	public boolean pruefeDatum(String geburtsdatum, String eintrittsdatum, String austrittsdatum) {
		boolean result = false;
		DatumPruefer d = new DatumPruefer();
		try {
			if (d.datumOK(geburtsdatum)) {result = true;} else {result = false;}
		} catch (Exception e) {
			e.printStackTrace();
		}
		try {
			if (d.datumOK(eintrittsdatum)) {result = true;} else {result = false;}
		} catch (Exception e) {
			e.printStackTrace();
		}		
		try {
			if (d.datumOK(austrittsdatum)) {result = true;} else {result = false;}
			// wenn kein Austrittsdatum angelegt werden kann dann trotzdem ok !
			if (austrittsdatum == "") {result = true;}
		} catch (Exception e) {
			e.printStackTrace();
		}		
		return result;
	}

	
	public int findeUrlaubstagedesMitarbeitersimJahr(int idm, int imjahr) {
		int result = 0;  // wenn null dann hat Mitarbeiter keine Urlaubstage im Jahr
		Set<Urlaubsanspruch> uset = findById(idm).getUrlaubsanspruechedesmitarbeiters();
		for (Urlaubsanspruch urlaubsanspruch : uset) {
			if (Integer.parseInt(urlaubsanspruch.getJahr().getJahr()) == imjahr) {
				result = urlaubsanspruch.getAnzahltage();
			}
		}
		return result;
	}

	/**
	 * Alle Abwesenheiten l&ouml;schen, die im Jahr des Urlaubsanspruches liegen und genehmigt waren
	 * @param idm
	 * @param u
	 */
	
	public Set<MitarbeiterAbwesend> gibAbwesenheitendiengenehmigtfuerMitarbeiterimJahr(int idm, Urlaubsanspruch u) {
		Calendar cal = new GregorianCalendar();
		int tempjahr = 0;
		Mitarbeiter m = findById(idm);
		Set<MitarbeiterAbwesend> result = new HashSet<MitarbeiterAbwesend>();
		Set<MitarbeiterAbwesend> mset = m.getAbwesenheitendesmitarbeiters();
		Set<Urlaubsanspruch> uset = m.getUrlaubsanspruechedesmitarbeiters();
		for (Urlaubsanspruch urlaubsanspruch : uset) {
			if (urlaubsanspruch.equals(u)) {
				tempjahr = Integer.parseInt(u.getJahr().getJahr());
			}
		}
		for (MitarbeiterAbwesend ma : mset) {
			cal.setTime(ma.getVonDatum());
			int jahr = cal.get(Calendar.YEAR);
			if (jahr == tempjahr) {
				if ((ma.getStatus()).equals("genehmigt")) {
					result.add(ma);
				}
			}
		}
		for (MitarbeiterAbwesend mx : result) {
			System.out.println(mx.getVonDatum());
		}
		return result;
	}		
}